#include "W5500_TCP.h"

//ServerIP
uint8_t server_ip[4]={192,168,26,125};

//开始 循环调用 因为要不停的初始化
void W5500_Server_Start(void){
    //1.判断是否为关闭状态
    //服务器创建，只执行一次
    uint8_t sn_status=getSn_SR(SN);
    if(sn_status==SOCK_CLOSED){
        //初始化socket0 ,成功返回第几个socket被初始化，也就是0
        //flag要看函数内部分支SF_TCP_NODELAY不延时就是不批处理，不多条数据一起执行
        uint8_t socket_num=socket(SN,Sn_MR_TCP,SERVER_PORT,SF_TCP_NODELAY);
        if(socket_num==SN){
            printf("socket0 init success\n");
        }
        else{
            printf("socket0 init failed\n");
        }
    }
    //2.不是close状态，则判断是否为初始化状态
    //为初始化状态则开启监听 监听成功并收到客户端连接（三次握手）后进入连接状态
    else if(sn_status==SOCK_INIT){
        uint8_t listen_status= listen(SN);
        if(listen_status==SOCK_OK){
            printf("listen success\n");
        }
        else{
            printf("listen failed\n");
        }
    }
    //3.对方（客户端）发了关闭请求（四次挥手后），则状态变为关闭等待
    else if(sn_status==SOCK_CLOSE_WAIT){
        printf("close\n");
         //回关闭请求（彻底关掉socket0，使其恢复CLOSE状态）
        close(SN);
    }   
}

//发送数据到缓冲区（缓冲区再通过网线传输）
void W5500_Server_Send(uint8_t *data,uint16_t len){
    uint8_t sn_status=getSn_SR(SN);
    //4.如果为连接状态(三次握手完成)，则发送数据
    if(sn_status==SOCK_ESTABLISHED){
        send(SN,data,len);
        printf("send over\n");
    }
}

//服务端从缓冲区接收数据
void W5500_Server_Recv(uint8_t *data,uint16_t *len){
    //因为接收和发送共用一个数组所以清空一下
    memset(data,0,*len);
    *len=0;
    uint8_t sn_status=getSn_SR(SN);
    //1.判断是否在连接状态
    if(sn_status==SOCK_ESTABLISHED){
        //2.判断缓冲区是否有数据(中断标志位为1)
        if((getSn_IR(SN)&Sn_IR_RECV)!=0){
            //为了知道是谁发过来的所以加个IP和端口号
            uint8_t ip[4];
            getSn_DIPR(SN,ip);  //获取IP(都有寄存器)
            uint16_t port=getSn_PORT(SN);  //获取端口号
            printf("[IP:%d.%d.%d.%d port:%d] ",ip[0],ip[1],ip[2],ip[3],port);

            //接收数据长度(先知道长度)
            *len=getSn_RX_RSR(SN);
            //接收数据（才能收数据）
            recv(SN,data,*len);
            //清空中断标志位（要把这位再置1才清空）
            setSn_IR(SN,Sn_IR_RECV);
            printf("%s\n",(char *)data);
        }
        
    }
}

//客户端开始 循环调用 因为要不停的初始化，接收到数据以后也要初始化tcp
void W5500_Cilent_Start(void){
    uint8_t sn_status=getSn_SR(SN);
    //判断状态是否为close,是则初始化
    if(sn_status==SOCK_CLOSED){
        //flag功能位=0，默认不延时（不批处理）
        uint8_t cilent_status= socket(SN,Sn_MR_TCP,CILENT_PORT,0);
        //判断初始化成功否（成功：socket号 不成功：错误码）
        if(cilent_status==SN){
            printf("socket0 init success\n");
        }
        else{
            printf("socket0 init failed\n");
        }
    }
    //如果已经初始化了，则准备主动连接到服务端
    else if(sn_status==SOCK_INIT){
        //客户端的ip和端口
        uint8_t connect_status=connect(SN,server_ip,SERVER_PORT);
        //连接成功，状态变为ES
        if(connect_status==SOCK_OK){
            printf("connect success\n");
        }
        else{
            printf("connect failed\n");
        }
    }
    else if(sn_status==SOCK_CLOSE_WAIT){
        printf("close\n");
        close(SN);
    }
}

//客户端发送数据到缓冲区（缓冲区再通过网线传输）
void W5500_Cilent_Send(uint8_t *data,uint16_t len){
    uint8_t sn_status=getSn_SR(SN);
    //判断是否为连接状态
    if(sn_status==SOCK_ESTABLISHED){
        send(SN,data,len);
        // printf("send over\n");
    }
}

//客户端从缓冲区接收数据
void W5500_Cilent_Recv(uint8_t *data,uint16_t *len){
    //重置一下数组
    memset(data,0,*len);
    *len=0;
    //如果状态为连接状态，则接收数据
    uint8_t sn_status=getSn_SR(SN);
    //1.判断是否为连接状态
    if(sn_status==SOCK_ESTABLISHED){
        //2.判断缓冲区是否有数据(中断标志位为1)
        if(getSn_IR(SN)&Sn_IR_RECV){
            //接收缓冲区大小
            *len=getSn_RX_RSR(SN);
            //接收数据
            recv(SN,data,*len);
            //重置标志位，设1则自动重置
            setSn_IR(SN,Sn_IR_RECV);
            printf("%s,len=%d\n",(char *)data,*len);
        }
    }
}

